<?xml version="1.0" encoding="UTF-8"?>
<!-- CityGML Version No. 1.0.0, May 19th, 2008-->
<!-- CityGML - GML3 application schema for the 3D city model of the Special Interest Group 3D (SIG 3D) of GDI NRW-->
<!-- Editors: PD Dr. Gerhard Groeger, Institute for Geodesy and Geoinformation, University of Bonn & -->
<!-- Prof. Dr. Thomas H. Kolbe, Institute for Geodesy and Geoinformation Science, Technical University of Berlin -->
<!-- For further information see: www.citygml.org -->
<!-- For the history of changes and additions to this CityGML schema see file history.txt -->
<xs:schema xmlns="http://www.opengis.net/citygml/appearance/1.0" xmlns:core="http://www.opengis.net/citygml/1.0"
    xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:gml="http://www.opengis.net/gml"
    targetNamespace="http://www.opengis.net/citygml/appearance/1.0" elementFormDefault="qualified"
    attributeFormDefault="unqualified">
    <xs:import namespace="http://www.opengis.net/gml" schemaLocation="http://schemas.opengis.net/gml/3.1.1/base/gml.xsd"/>
    <xs:import namespace="http://www.opengis.net/citygml/1.0" schemaLocation="http://schemas.opengis.net/citygml/1.0/cityGMLBase.xsd"/>
    <!-- ========================================================================================= -->
    <!-- ======================CityGML Appearance module ============================================ -->
    <!-- ========================================================================================= -->
    <xs:complexType name="AppearanceType">
        <xs:annotation>
            <xs:documentation> Named container for all surface data (texture/material). All appearances of the same name ("theme")
                within a CityGML file are considered a group. </xs:documentation>
        </xs:annotation>
        <xs:complexContent>
            <xs:extension base="gml:AbstractFeatureType">
                <xs:sequence>
                    <xs:element name="theme" type="xs:string" minOccurs="0"/>
                    <xs:element name="surfaceDataMember" type="SurfaceDataPropertyType" minOccurs="0" maxOccurs="unbounded"/>
                    <xs:element ref="_GenericApplicationPropertyOfAppearance" minOccurs="0" maxOccurs="unbounded"/>
                </xs:sequence>
            </xs:extension>
        </xs:complexContent>
    </xs:complexType>
    <!-- ========================================================================================= -->
    <xs:element name="_GenericApplicationPropertyOfAppearance" type="xs:anyType" abstract="true"/>
    <!-- ========================================================================================= -->
    <xs:complexType name="AppearancePropertyType">
        <xs:annotation>
            <xs:documentation>Denotes the relation of a _CityObject resp. CityModel to its appearances. The AppearancePropertyType
                element must either carry a reference to a Appearance object or contain a Appearance object inline, but neither
                both nor none.</xs:documentation>
        </xs:annotation>
        <xs:complexContent>
            <xs:extension base="gml:FeaturePropertyType">
                <xs:sequence minOccurs="0">
                    <xs:element name="Appearance" type="AppearanceType"/>
                </xs:sequence>
            </xs:extension>
        </xs:complexContent>
    </xs:complexType>
    <!-- ========================================================================================= -->
    <xs:element name="appearanceMember" type="AppearancePropertyType" substitutionGroup="gml:featureMember"/>
    <!-- ========================================================================================= -->
    <xs:element name="appearance" type="AppearancePropertyType" substitutionGroup="core:_GenericApplicationPropertyOfCityObject"/>
    <!-- ========================================================================================= -->
    <xs:complexType name="AbstractSurfaceDataType">
        <xs:annotation>
            <xs:documentation>Base class for textures and material. Contains only isFront-flag.</xs:documentation>
        </xs:annotation>
        <xs:complexContent>
            <xs:extension base="gml:AbstractFeatureType">
                <xs:sequence>
                    <xs:element name="isFront" type="xs:boolean" default="true" minOccurs="0"/>
                    <xs:element ref="_GenericApplicationPropertyOfSurfaceData" minOccurs="0" maxOccurs="unbounded"/>
                </xs:sequence>
            </xs:extension>
        </xs:complexContent>
    </xs:complexType>
    <!-- ========================================================================================= -->
    <xs:element name="_SurfaceData" type="AbstractSurfaceDataType" abstract="true" substitutionGroup="gml:_Feature"/>
    <!-- ========================================================================================= -->
    <xs:element name="_GenericApplicationPropertyOfSurfaceData" type="xs:anyType" abstract="true"/>
    <!-- ========================================================================================= -->
    <xs:complexType name="SurfaceDataPropertyType">
        <xs:annotation>
            <xs:documentation>Denotes the relation of an Appearance to its surface data. The SurfaceDataPropertyType element must
                either carry a reference to a _SurfaceData object or contain a _SurfaceData object inline, but neither both nor
                none.</xs:documentation>
        </xs:annotation>
        <xs:sequence minOccurs="0">
            <xs:element ref="_SurfaceData" minOccurs="0"/>
        </xs:sequence>
        <xs:attributeGroup ref="gml:AssociationAttributeGroup"/>
    </xs:complexType>
    <!-- ========================================================================================= -->
    <xs:complexType name="AbstractTextureType">
        <xs:annotation>
            <xs:documentation>Base class for textures. "imageURI" can contain any valid URI from references to a local file to
                preformatted web service requests. The linking to geometry and texture parameterization is provided by derived
                classes.</xs:documentation>
        </xs:annotation>
        <xs:complexContent>
            <xs:extension base="AbstractSurfaceDataType">
                <xs:sequence>
                    <xs:element name="imageURI" type="xs:anyURI"/>
                    <xs:element name="mimeType" type="core:MimeTypeType" minOccurs="0"/>
                    <xs:element name="textureType" type="TextureTypeType" minOccurs="0"/>
                    <xs:element name="wrapMode" type="WrapModeType" minOccurs="0"/>
                    <xs:element name="borderColor" type="ColorPlusOpacity" minOccurs="0"/>
                    <xs:element ref="_GenericApplicationPropertyOfTexture" minOccurs="0" maxOccurs="unbounded"/>
                </xs:sequence>
            </xs:extension>
        </xs:complexContent>
    </xs:complexType>
    <!-- ========================================================================================= -->
    <xs:element name="_Texture" type="AbstractTextureType" abstract="true" substitutionGroup="_SurfaceData"/>
    <!-- ========================================================================================= -->
    <xs:element name="_GenericApplicationPropertyOfTexture" type="xs:anyType" abstract="true"/>
    <!-- ========================================================================================= -->
    <xs:simpleType name="WrapModeType">
        <xs:annotation>
            <xs:documentation>Fill mode for a texture. "wrap" repeats the texture, "clamp" extends the edges of the texture, and
                "border" fills all undefined areas with "borderColor"</xs:documentation>
        </xs:annotation>
        <xs:restriction base="xs:string">
            <xs:enumeration value="none"/>
            <xs:enumeration value="wrap"/>
            <xs:enumeration value="mirror"/>
            <xs:enumeration value="clamp"/>
            <xs:enumeration value="border"/>
        </xs:restriction>
    </xs:simpleType>
    <!-- ========================================================================================= -->
    <xs:complexType name="ParameterizedTextureType">
        <xs:annotation>
            <xs:documentation>Specialization for standard 2D textures. "target" provides the linking to surface geometry. Only
                gml:MultiSurface and decendants of gml:AbstractSurfaceType are valid targets. As property of the link, a texture
                parameterization either as set of texture coordinates or transformation matrix is given. </xs:documentation>
        </xs:annotation>
        <xs:complexContent>
            <xs:extension base="AbstractTextureType">
                <xs:sequence>
                    <xs:element name="target" type="TextureAssociationType" minOccurs="0" maxOccurs="unbounded"/>
                    <xs:element ref="_GenericApplicationPropertyOfParameterizedTexture" minOccurs="0" maxOccurs="unbounded"/>
                </xs:sequence>
            </xs:extension>
        </xs:complexContent>
    </xs:complexType>
    <!-- ========================================================================================= -->
    <xs:element name="ParameterizedTexture" type="ParameterizedTextureType" substitutionGroup="_Texture"/>
    <!-- ========================================================================================= -->
    <xs:element name="_GenericApplicationPropertyOfParameterizedTexture" type="xs:anyType" abstract="true"/>
    <!-- ========================================================================================= -->
    <xs:complexType name="GeoreferencedTextureType">
        <xs:annotation>
            <xs:documentation>Specialization for georeferenced textures, i.e. textures using a planimetric projection. Such
                textures contain an implicit parameterization (either stored within the image file, in an acompanying world file,
                or using the "referencePoint" and "orientation"-elements). A georeference provided by "referencePoint" and
                "orientation" always takes precedence. The search order for an external georeference is determined by the boolean
                flag preferWorldFile. If this flag is set to true (its default value), a world file is looked for first and only
                if it is not found the georeference from the image data is used. If preferWorldFile is false, the world file is
                used only if no georeference from the image data is available. The "boundedBy"-property should contain the
                bounding box of the projected image data. Since a georeferenced texture has a unique parameterization, "target"
                only provides links to surface geometry without any additional texture parameterization. Only gml:MultiSurface or
                decendants of gml:AbstractSurfaceType are valid targets.</xs:documentation>
        </xs:annotation>
        <xs:complexContent>
            <xs:extension base="AbstractTextureType">
                <xs:sequence>
                    <xs:element name="preferWorldFile" type="xs:boolean" default="true" minOccurs="0"/>
                    <xs:element name="referencePoint" type="gml:PointPropertyType" minOccurs="0"/>
                    <xs:element name="orientation" type="core:TransformationMatrix2x2Type" minOccurs="0"/>
                    <xs:element name="target" type="xs:anyURI" minOccurs="0" maxOccurs="unbounded"/>
                    <xs:element ref="_GenericApplicationPropertyOfGeoreferencedTexture" minOccurs="0" maxOccurs="unbounded"/>
                </xs:sequence>
            </xs:extension>
        </xs:complexContent>
    </xs:complexType>
    <!-- ========================================================================================= -->
    <xs:element name="GeoreferencedTexture" type="GeoreferencedTextureType" substitutionGroup="_Texture"/>
    <!-- ========================================================================================= -->
    <xs:element name="_GenericApplicationPropertyOfGeoreferencedTexture" type="xs:anyType" abstract="true"/>
    <!-- ========================================================================================= -->
    <xs:complexType name="TextureAssociationType">
        <xs:annotation>
            <xs:documentation>Denotes the relation of a texture to a surface, that is augmented by a TextureParameterization
                object. The TextureAssociationType element must either carry a reference to a _TextureParameterization object or
                contain a _TextureParameterization object inline, but neither both nor none.</xs:documentation>
        </xs:annotation>
        <xs:sequence minOccurs="0">
            <xs:element ref="_TextureParameterization"/>
        </xs:sequence>
        <xs:attribute name="uri" type="xs:anyURI" use="required"/>
        <xs:attributeGroup ref="gml:AssociationAttributeGroup"/>
    </xs:complexType>
    <!-- ========================================================================================= -->
    <xs:complexType name="AbstractTextureParameterizationType" abstract="true">
        <xs:annotation>
            <xs:documentation>Base class for augmenting a link "texture->surface" with texture parameterization. Subclasses of
                this class define concrete parameterizations. Currently, texture coordinates and texture coordinate generation
                using a transformation matrix are available. </xs:documentation>
        </xs:annotation>
        <xs:complexContent>
            <xs:extension base="gml:AbstractGMLType">
                <xs:sequence>
                    <xs:element ref="_GenericApplicationPropertyOfTextureParameterization" minOccurs="0" maxOccurs="unbounded"/>
                </xs:sequence>
            </xs:extension>
        </xs:complexContent>
    </xs:complexType>
    <!-- ========================================================================================= -->
    <xs:element name="_TextureParameterization" type="AbstractTextureParameterizationType" abstract="true"
        substitutionGroup="gml:_GML"/>
    <!-- ========================================================================================= -->
    <xs:element name="_GenericApplicationPropertyOfTextureParameterization" type="xs:anyType" abstract="true"/>
    <!-- ========================================================================================= -->
    <xs:complexType name="TexCoordListType">
        <xs:annotation>
            <xs:documentation>Texture parameterization using texture coordinates: Each gml:LinearRing that is part of the surface
                requires a separate "textureCoordinates"-entry with 2 doubles per ring vertex. The "ring"- attribute provides the
                gml:id of the target LinearRing. It is prohibited to link texture coordinates to any other object type than
                LinearRing. Thus, surfaces not consisting of LinearRings cannot be textured this way. Use transformation matrices
                (see below) or georeferenced textures instead. </xs:documentation>
        </xs:annotation>
        <xs:complexContent>
            <xs:extension base="AbstractTextureParameterizationType">
                <xs:sequence>
                    <xs:element name="textureCoordinates" maxOccurs="unbounded">
                        <xs:complexType>
                            <xs:simpleContent>
                                <xs:extension base="gml:doubleList">
                                    <xs:attribute name="ring" type="xs:anyURI" use="required"/>
                                </xs:extension>
                            </xs:simpleContent>
                        </xs:complexType>
                    </xs:element>
                    <xs:element ref="_GenericApplicationPropertyOfTexCoordList" minOccurs="0" maxOccurs="unbounded"/>
                </xs:sequence>
            </xs:extension>
        </xs:complexContent>
    </xs:complexType>
    <!-- ========================================================================================= -->
    <xs:element name="TexCoordList" type="TexCoordListType" substitutionGroup="_TextureParameterization"/>
    <!-- ========================================================================================= -->
    <xs:element name="_GenericApplicationPropertyOfTexCoordList" type="xs:anyType" abstract="true"/>
    <!-- ========================================================================================= -->
    <xs:complexType name="TexCoordGenType">
        <xs:annotation>
            <xs:documentation>Texture parameterization using a transformation matrix. The transformation matrix "worldToTexture"
                can be used to derive texture coordinates from an object's location. This 3x4 matrix T computes the coordinates
                (s,t) from a homogeneous world position p as (s,t) = (s'/q', t'/q') with (s', t', q') = T*p. Thus, perspective
                projections can be specified. The SRS can be specified using standard attributes. If an object is given in a
                different reference system, it is transformed to the SRS before applying the transformation. A transformation
                matrix can be used for whole surfaces. It is not required to specify it per LinearRing. </xs:documentation>
        </xs:annotation>
        <xs:complexContent>
            <xs:extension base="AbstractTextureParameterizationType">
                <xs:sequence>
                    <xs:element name="worldToTexture">
                        <xs:complexType>
                            <xs:simpleContent>
                                <xs:extension base="core:TransformationMatrix3x4Type">
                                    <xs:attributeGroup ref="gml:SRSReferenceGroup"/>
                                </xs:extension>
                            </xs:simpleContent>
                        </xs:complexType>
                    </xs:element>
                    <xs:element ref="_GenericApplicationPropertyOfTexCoordGen" minOccurs="0" maxOccurs="unbounded"/>
                </xs:sequence>
            </xs:extension>
        </xs:complexContent>
    </xs:complexType>
    <!-- ========================================================================================= -->
    <xs:element name="TexCoordGen" type="TexCoordGenType" substitutionGroup="_TextureParameterization"/>
    <!-- ========================================================================================= -->
    <xs:element name="_GenericApplicationPropertyOfTexCoordGen" type="xs:anyType" abstract="true"/>
    <!-- ========================================================================================= -->
    <xs:complexType name="X3DMaterialType">
        <xs:annotation>
            <xs:documentation>Class for defining constant surface properties. It is based on X3D's material definition. In
                addition, "isSmooth" provides a hint for value interpolation. The link to surface geometry is established via the
                "target"-property. Only gml:MultiSurface or decendants of gml:AbstractSurfaceType are valid targets.
            </xs:documentation>
        </xs:annotation>
        <xs:complexContent>
            <xs:extension base="AbstractSurfaceDataType">
                <xs:sequence>
                    <xs:element name="ambientIntensity" type="core:doubleBetween0and1" default="0.2" minOccurs="0"/>
                    <xs:element name="diffuseColor" type="Color" default="0.8 0.8 0.8" minOccurs="0"/>
                    <xs:element name="emissiveColor" type="Color" default="0.0 0.0 0.0" minOccurs="0"/>
                    <xs:element name="specularColor" type="Color" default="1.0 1.0 1.0" minOccurs="0"/>
                    <xs:element name="shininess" type="core:doubleBetween0and1" default="0.2" minOccurs="0"/>
                    <xs:element name="transparency" type="core:doubleBetween0and1" default="0.0" minOccurs="0"/>
                    <xs:element name="isSmooth" type="xs:boolean" default="false" minOccurs="0"/>
                    <xs:element name="target" type="xs:anyURI" minOccurs="0" maxOccurs="unbounded"/>
                    <xs:element ref="_GenericApplicationPropertyOfX3DMaterial" minOccurs="0" maxOccurs="unbounded"/>
                </xs:sequence>
            </xs:extension>
        </xs:complexContent>
    </xs:complexType>
    <!-- ========================================================================================= -->
    <xs:element name="X3DMaterial" type="X3DMaterialType" substitutionGroup="_SurfaceData"/>
    <!-- ========================================================================================= -->
    <xs:element name="_GenericApplicationPropertyOfX3DMaterial" type="xs:anyType" abstract="true"/>
    <!-- ========================================================================================= -->
    <xs:simpleType name="TextureTypeType">
        <xs:annotation>
            <xs:documentation>Textures can be qualified by the attribute textureType. The textureType differentiates between
                textures, which are specific for a certain object and are only used for that object (specific), and prototypic
                textures being typical for that kind of object and are used many times for all objects of that kind (typical). A
                typical texture may be replaced by a specific, if available. Textures may also be classified as unknown.
            </xs:documentation>
        </xs:annotation>
        <xs:restriction base="xs:string">
            <xs:enumeration value="specific"/>
            <xs:enumeration value="typical"/>
            <xs:enumeration value="unknown"/>
        </xs:restriction>
    </xs:simpleType>
    <!-- ========================================================================================= -->
    <xs:simpleType name="Color">
        <xs:annotation>
            <xs:documentation>List of three values (red, green, blue), separated by spaces. The values must be in the range
                between zero and one. </xs:documentation>
        </xs:annotation>
        <xs:restriction base="core:doubleBetween0and1List">
            <xs:length value="3"/>
        </xs:restriction>
    </xs:simpleType>
    <!-- ========================================================================================= -->
    <xs:simpleType name="ColorPlusOpacity">
        <xs:annotation>
            <xs:documentation>List of three or four values (red, green, blue, opacity), separated by spaces. The values must be in
                the range between zero and one. If no opacity is given, it is assumed as 1.0.</xs:documentation>
        </xs:annotation>
        <xs:restriction base="core:doubleBetween0and1List">
            <xs:minLength value="3"/>
            <xs:maxLength value="4"/>
        </xs:restriction>
    </xs:simpleType>
    <!-- ========================================================================================= -->
</xs:schema>
